
package date0528_1;
/**
 * 1、深克隆 : 不仅克隆当前对象本身，连当前对象关联的其它对象也克隆
 * 2、注意 字符串是不能克隆的，字符串类型具有不可编译性，不可克隆，没有后代
 */
public class Pig extends Object implements Cloneable {
	
	private String name ; // 引用类型
	
	private int age ; // 基本类型
	
	private Master master ; // 引用类型

	public Pig(String name , int age , Master master ) {
		super();
		this.name = name;
		this.age = age ;
		this.master = master ;
	}
	
	@Override
	public Object clone() throws CloneNotSupportedException { 
		
		Object o = super.clone() ; // 仍然是调用由 Object 提供的 clone 支持 ( 一定要调用 )
		
		if( o != null ) {
			// 将 变量 o 中存储的 地址 赋值给 变量 p 并转换类型
			Pig p = (Pig) o ;
			
			// name 是 java.lang.String 类型，而 String 从 Object 继承的 clone 方法 修饰符是 protected
			// String 类没有子类，因此 不可能通过 String 子类来调用其 clone 方法 ( Pig 也不是 String 的子类 )
			// Pig 与 String 类不在同一个包中，因此不能够调用 Stirng 类的 clone 方法
			
			// p.name = (String)this.name.clone();//字符串具有不可编译性，不可克隆，没有后代
			
			p.master = (Master)this.master.clone(); // 把 master 也克隆
		}
		
		return o ; // 要理解 变量 o 和 变量 p 指向的 是同一个对象
	}

	public static void main(String[] args) throws CloneNotSupportedException {
		
		Master a = new Master( "唐三藏" );
		
		Pig m = new Pig( "猪悟能"  , 1200 , a );
		
		
		Object o = m.clone();
		
		System.out.println( m == o ); // false
		
		Pig n = (Pig) o ;
		System.out.println( m == n ); // false
		
		System.out.println( "~ ~ ~ ~ ~ ~ ~" );
		
		// == 比较两个变量所存储的值
		System.out.println( m.name == n.name ); // true
		System.out.println( m.age == n.age ); // true : 比较基本数据类型的值
		System.out.println( m.master == n.master ); // false : 说明内部关联的对象没有被克隆
		
	}

}
